package com.geekstudy.week10.config;


import com.geekstudy.week10.api.UserApi;
import com.geekstudy.week10.service.SupplierService;
import io.github.resilience4j.bulkhead.*;
import io.vavr.control.Try;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

import java.time.Duration;
import java.util.function.Supplier;

@Configuration
public class Resilience4jBulkheadConfiguration {


    @Autowired
    private SupplierService supplierService;

    @Bean
    public Bulkhead bulkhead() {
        // custom a configuration for a Bulkhead
        int maxConcurrentCalls = 150;
        Duration maxWaitDuration = Duration.ofSeconds(0);
        // boolean writableStackTraceEnabled = true;
        // boolean fairCallHandlingEnabled = true;



        // BulkheadConfig bulkheadConfig = BulkheadConfig.ofDefaults();
        BulkheadConfig bulkheadConfig = (BulkheadConfig.custom()
                .maxConcurrentCalls(maxConcurrentCalls)
                .maxWaitDuration(maxWaitDuration)
                .writableStackTraceEnabled(true)
                .fairCallHandlingStrategyEnabled(true)).build();


        // BulkheadRegistry bulkheadRegistry = BulkheadRegistry.ofDefaults();
        BulkheadRegistry bulkheadRegistry = BulkheadRegistry.of(bulkheadConfig);

        Bulkhead userBulk = bulkheadRegistry.bulkhead("userBulk");
        Supplier<String> decoratedSupplier = Bulkhead.decorateSupplier(userBulk, supplierService::get);
        String result = Try.ofSupplier(decoratedSupplier).get();
        System.out.println(" result:" + result);


        return userBulk;
        // ThreadPoolBulkheadRegistry threadPoolBulkheadRegistry = ThreadPoolBulkheadRegistry.ofDefaults();

    }

    @Bean
    public ThreadPoolBulkheadRegistry threadPoolBulkheadRegistry() {
        ThreadPoolBulkheadConfig threadPoolBulkheadConfig = ThreadPoolBulkheadConfig.custom()
                .maxThreadPoolSize(150).coreThreadPoolSize(10)
                .queueCapacity(50).build();

        ThreadPoolBulkheadRegistry threadPoolBulkheadRegistry = ThreadPoolBulkheadRegistry.of(threadPoolBulkheadConfig);

        return threadPoolBulkheadRegistry;
    }

    @Bean
    public ThreadPoolBulkhead threadPoolBulkHead() {
        ThreadPoolBulkheadRegistry threadPoolBulkheadRegistry = threadPoolBulkheadRegistry();
        ThreadPoolBulkhead threadPoolBulkhead = threadPoolBulkheadRegistry.bulkhead("demo2021");
        return threadPoolBulkhead;
    }

}
